/*
 * Copyright (C) 2021 Huawei Device Co., Ltd.
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *     http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

package com.example.distschedule.slice;

import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONObject;
import com.example.distschedule.ResourceTable;
import com.example.distschedule.bean.Command;
import com.example.distschedule.bean.DeviceResult;
import com.example.distschedule.bean.RespondBase;
import com.example.distschedule.rx2.OKHttpUtilsRx2;
import com.example.distschedule.toast.XToast;
import com.example.distschedule.toast.XToastUtils;
import com.example.distschedule.utils.CommandUtil;
import com.example.distschedule.utils.DeviceStateUtil;
import com.example.distschedule.utils.PreferencesUtil;
import com.socks.library.KLog;
import ohos.aafwk.ability.AbilitySlice;
import ohos.aafwk.content.Intent;
import ohos.agp.components.*;
import ohos.agp.utils.Color;
import ohos.app.dispatcher.TaskDispatcher;
import ohos.app.dispatcher.task.TaskPriority;
import ohos.miscservices.timeutility.Time;
import okhttp3.MediaType;
import okhttp3.RequestBody;

import java.util.Locale;

/**
 * 门铃控制页面
 */
public class DoorbellAbilitySlice extends AbilitySlice {
    private boolean isON = false;
    private String deviceId;
    private Text doorSwitchState;
    private Image doorImg;
    private Text stateLeftText;
    private Text stateMainText;
    private Text stateSubText;
    private DirectionalLayout batteryDl;
    private Image closeAlarmImage;
    private Image deviceLogo;

    @Override
    public void onStart(Intent intent) {
        super.onStart(intent);
        super.setUIContent(ResourceTable.Layout_ability_doorbell);

        deviceId = intent.getStringParam("deviceId");
        initComponents();
        initDeviceState();
    }

    private void initNetState() {
        TaskDispatcher globalTaskDispatcher = getGlobalTaskDispatcher(TaskPriority.DEFAULT);
        globalTaskDispatcher.asyncDispatch(() -> {
            KLog.i("async task initNetState run");
            checkDeviceNet();
        });
    }

    private void initDeviceState() {
        // 从服务端获取设备信息
        OKHttpUtilsRx2.INSTANCE.getApi().getDeviceInfo(deviceId, PreferencesUtil.getUserId(getContext()))
                .compose(OKHttpUtilsRx2.INSTANCE.ioMain())
                .subscribe(new OKHttpUtilsRx2.SubjectImpl<RespondBase<DeviceResult>>() {
                    @Override
                    public void onNext(RespondBase<DeviceResult> deviceInfo) {
                        KLog.i(deviceInfo);
                        if (deviceInfo.isSuccess() && deviceInfo.getResult().isOnline()) {
                            updateData(deviceInfo.getResult().getProperty());
                        } else {
                            initNetState();
                        }
                    }

                    @Override
                    public void onError(Throwable throwable) {
                        initNetState();
                    }
                });
    }

    private void updateData(String property) {
        // 更新状态
        String[] deviceDataList = DeviceStateUtil.getKeyValue(property, "LockStatus", "DoorBellStatus", "Beep");
        isON = "ON".equals(deviceDataList[0]);
        String doorBellStatus = deviceDataList[1];
        boolean isBeepOpen = "ON".equals(deviceDataList[2]);

        if (isON) {
            doorImg.setPixelMap(ResourceTable.Media_icon_open_door);
            doorSwitchState.setTextColor(new Color(getColor(ResourceTable.Color_blue)));
        } else {
            doorImg.setPixelMap(ResourceTable.Media_icon_close_door);
            doorSwitchState.setTextColor(new Color(getColor(ResourceTable.Color_black)));
        }
        switch (doorBellStatus) {
            // 无人靠近
            case "NO_PERSON_APPROACH": {
                setNoOneState();
                break;
            }
            // 访客唤铃
            case "CALLING_BELL": {
                KLog.i(isBeepOpen + deviceDataList[2]);
                setRingState();
                if (isBeepOpen) {
                    showStopImage(false);
                } else {
                    hideStopImage();
                }
                break;
            }
            case "UNKNOWN_PERSON_APPROACH": {
                // 报警蜂鸣器是否打开
                if (isBeepOpen) {
                    setAlarmState();
                } else {
                    setCloseAlarmState();
                }
                break;
            }
            default: {
                setNoOneState();
                KLog.e(doorBellStatus);
                XToastUtils.toast("设备上报属性错误：" +doorBellStatus);
            }
        }
    }

    private void checkDeviceNet() {
        Time.sleep(15 * 1000);
        OKHttpUtilsRx2.INSTANCE.getApi().getDeviceInfo(deviceId, PreferencesUtil.getUserId(getContext()))
                .compose(OKHttpUtilsRx2.INSTANCE.ioMain())
                .subscribe(new OKHttpUtilsRx2.SubjectImpl<RespondBase<DeviceResult>>() {
                    @Override
                    public void onNext(RespondBase<DeviceResult> deviceInfo) {
                        super.onNext(deviceInfo);
                        KLog.i(deviceInfo);
                        if (deviceInfo.getResult() == null || !deviceInfo.getResult().isOnline()) {
                            XToastUtils.toast("未配网成功，请再次碰一碰重试");
                        }
                    }
                });
    }

    private void initComponents() {
        // 设备图片
        deviceLogo = (Image) findComponentById(ResourceTable.Id_doorbell_image_logo);
        // 状态文本
        stateLeftText = (Text) findComponentById(ResourceTable.Id_doorbell_text_state_left);
        stateMainText = (Text) findComponentById(ResourceTable.Id_doorbell_text_state_main);
        stateSubText = (Text) findComponentById(ResourceTable.Id_doorbell_text_state_sub);
        // 右侧电池/停止报警按钮
        batteryDl = (DirectionalLayout) findComponentById(ResourceTable.Id_doorbell_dl_battery);
        closeAlarmImage = (Image) findComponentById(ResourceTable.Id_doorbell_image_close);
        closeAlarmImage.setClickedListener(this::stopAlarm);
        // 开门
        doorImg = (Image) findComponentById(ResourceTable.Id_doorbell_image_door);
        doorSwitchState = (Text) findComponentById(ResourceTable.Id_doorbell_text_door);
        findComponentById(ResourceTable.Id_doorbell_dl_door).setClickedListener(this::openDoor);
        // 返回
        findComponentById(ResourceTable.Id_doorbell_img_left).setClickedListener(this::goBack);
        // 安防报告
        findComponentById(ResourceTable.Id_doorbell_dl_report).setClickedListener(component -> {
            XToastUtils.toast("请到设备侧查看，FA暂不支持敬请期待");
        });
        // more
        findComponentById(ResourceTable.Id_doorbell_img_right).setClickedListener(component -> {
            XToastUtils.toast("智能门铃基于BES2600板子支持远程访客通知、不明人员长时间逗留报警和远程开关门等功能");
        });
        // 铃声
        Text doorbellValue = (Text) findComponentById(ResourceTable.Id_doorbell_text_bar_value);
        Slider doorbellSlider = (Slider) findComponentById(ResourceTable.Id_doorbell_slider_bar);
        doorbellSlider.setValueChangedListener(new Slider.ValueChangedListener() {
            @Override
            public void onProgressUpdated(Slider slider, int progress, boolean fromUser) {

            }

            @Override
            public void onTouchStart(Slider slider) {

            }

            @Override
            public void onTouchEnd(Slider slider) {
                XToastUtils.toast("设备暂不支持，敬请期待");
                doorbellValue.setText(String.format(Locale.CHINA, "%s", slider.getProgress() + "%"));
            }
        });
    }

    /**
     * 停止报警
     */
    private void stopAlarm(Component component) {
        sendCommand(CommandUtil.getDoorbellCloseAlarmCommand());
        setCloseAlarmState();
    }

    private void goBack(Component component) {
        onBackPressed();
    }

    private void openDoor(Component component) {
        isON = !isON;
        if (isON) {
            // 只能开门
            sendCommand(CommandUtil.getDoorbellOpenCommand());
            doorImg.setPixelMap(ResourceTable.Media_icon_open_door);
            doorSwitchState.setTextColor(new Color(getColor(ResourceTable.Color_blue)));
            // 5s后设备会自动锁门所以再获取次设备状态
            XToastUtils.info("开门5s后会自动上锁");
            TaskDispatcher globalTaskDispatcher = getGlobalTaskDispatcher(TaskPriority.DEFAULT);
            globalTaskDispatcher.asyncDispatch(() -> {
                Time.sleep(6 * 1000);
                initDeviceState();
            });
        }
    }

    /**
     * 设置无人状态
     */
    private void setNoOneState() {
        stateLeftText.setText("安防中");
        stateLeftText.setTextColor(new Color(getColor(ResourceTable.Color_black)));
        stateMainText.setText("无人");
        stateMainText.setTextColor(new Color(getColor(ResourceTable.Color_green)));
        stateSubText.setText("当前状态");
        hideStopImage();
    }

    /**
     * 设置响铃状态
     */
    private void setRingState() {
        stateLeftText.setText("安防中");
        stateLeftText.setTextColor(new Color(getColor(ResourceTable.Color_black)));
        stateMainText.setText("有人按铃");
        stateMainText.setTextColor(new Color(getColor(ResourceTable.Color_blue)));
        stateSubText.setText("当前状态");
    }

    /**
     * 设置报警状态
     */
    private void setAlarmState() {
        stateLeftText.setText("报警中");
        stateLeftText.setTextColor(new Color(getColor(ResourceTable.Color_red)));
        stateMainText.setText("00:03:00");
        stateMainText.setTextColor(new Color(getColor(ResourceTable.Color_black)));
        stateSubText.setText("有人长时间逗留");
        showStopImage(true);
    }

    /**
     * 设置已关闭报警状态
     */
    private void setCloseAlarmState() {
        stateLeftText.setText("已关闭");
        stateLeftText.setTextColor(new Color(getColor(ResourceTable.Color_red)));
        stateMainText.setText("00:03:00");
        stateMainText.setTextColor(new Color(getColor(ResourceTable.Color_black)));
        stateSubText.setText("有人长时间逗留");
        hideStopImage();
    }

    /**
     * 显示停止按钮
     */
    private void showStopImage(boolean isShowState) {
        if (isShowState){
            deviceLogo.setPixelMap(ResourceTable.Media_icon_device_alert);
        }
        batteryDl.setVisibility(Component.HIDE);
        closeAlarmImage.setVisibility(Component.VISIBLE);
    }

    /**
     * 隐藏停止按钮
     */
    private void hideStopImage() {
        deviceLogo.setPixelMap(ResourceTable.Media_img_doorbell);
        batteryDl.setVisibility(Component.VISIBLE);
        closeAlarmImage.setVisibility(Component.HIDE);
    }

    /**
     * 发送命令
     *
     * @param command 命令
     */
    private void sendCommand(Command command) {
        JSONObject body = new JSONObject();
        body.put("commandName", command.getCommandName());
        body.put("serviceId", command.getServiceId());
        body.put("value", command.getValue());
        OKHttpUtilsRx2.INSTANCE.getApi().sendCommand(deviceId,
                RequestBody.create(MediaType.parse("application/json;charset=UTF-8"), JSON.toJSONString(body)))
                .compose(OKHttpUtilsRx2.INSTANCE.ioMain())
                .subscribe(new OKHttpUtilsRx2.SubjectImpl<RespondBase>() {
                    @Override
                    public void onNext(RespondBase respond) {
                        super.onNext(respond);
                        if (respond.isSuccess()) {
                            XToastUtils.toast("控制命令发送成功");
                        }
                    }
                });
    }

    @Override
    public void onActive() {
        super.onActive();
    }

    @Override
    public void onForeground(Intent intent) {
        super.onForeground(intent);
    }
}
